//工具箱

const os = require("os");

NCUTCAT.tools = {};
let tool = NCUTCAT.tools;

NCUTCAT.tools.getMineTime = () => {
    var date = new Date();
    return date.getHours() + ":" + date.getMinutes() + ":" + date.getSeconds();
};

NCUTCAT.tools.inRange = (value, MIN, MAX) => {
    if (typeof value === "number") {
        return value >= MIN && value <= MAX;
    }
    if (typeof value === "string" || value instanceof Array) {
        return value.length >= MIN && value.length <= MAX;
    }
};

const crypto = require("crypto");
NCUTCAT.tools.md5 = (text) => {
    return crypto.createHash("md5").update(text).digest("hex");
};

NCUTCAT.tools.randomString = (len) => {
    len = len || 1024;
    var $chars = "ABCDEFGHIJKLNMOPQRSTUVWXYZabcdefghijklnmopqrstuvwxyz1234567890_";
    var maxPos = $chars.length;
    var pwd = "";
    for (let i = 0; i < len; i++) {
        pwd += $chars.charAt(Math.floor(Math.random() * maxPos));
    }
    return pwd;
};

NCUTCAT.tools.randomString_plus = (len) => {
    len = len || 8192;
    var $chars = "ABCDEFGHIJKLNMOPQRSTUVWXYZabcdefghijklnmopqrstuvwxyz1234567890_~!@#$%^&*()_+<>{}[]:;۞۞╳❤█♠♦★◐";
    var maxPos = $chars.length;
    var pwd = "";
    for (let i = 0; i < len; i++) {
        pwd += $chars.charAt(Math.floor(Math.random() * maxPos));
    }
    return pwd;
};

const fs = require("fs");
NCUTCAT.tools.autoLoadModule = (proPath, minePath, callback) => {
    let routeList = fs.readdirSync("./" + proPath);
    for (let key in routeList) {
        let name = routeList[key].replace(".js", "");
        try {
            callback("./" + minePath + name, proPath);
        } catch (err) {
            MCSERVER.error("autoLoadModule load 过程出错", err);
            throw err;
        }
    }
};

NCUTCAT.tools.mCopyFileSync = (oldpath, newpath) => {
    let resetData = fs.readFileSync(oldpath, {
        encoding: "UTF-8"
    });
    fs.writeFileSync(newpath, resetData, {
        encoding: "UTF-8"
    });
    return true;
};

NCUTCAT.tools.getSystemCodeing = () => {
    let auto_console_coding;
    if (os.platform() == "win32") auto_console_coding = "GBK";
    else auto_console_coding = "UTF-8";
    return auto_console_coding;
};

NCUTCAT.tools.getFullTime = () => {
    var date = new Date();
    return date.getFullYear() + "/" + date.getMonth() + "/" + date.getDay() + " " + date.getHours() + ":" + date.getMinutes() + ":" + date.getSeconds();
};

const REPALCE_STR = "__MCSMANAGER_REPLACE_STR__";
NCUTCAT.tools.CharReplaceTemp = (text = "", replaceStr = "") => {
    let re = new RegExp(replaceStr, "gim");
    text = text.replace(re, REPALCE_STR);
    return text;
};
NCUTCAT.tools.TempReplaceChar = (text = "", replaceStr = "") => {
    let re = new RegExp(REPALCE_STR, "gim");
    text = text.replace(re, replaceStr);
    return text;
};

NCUTCAT.tools.UUIDtoHex = (uuid) => {
    if (uuid.startsWith('0x')) uuid = uuid.substring(2);
    uuid = '0x' + uuid.replace(/[^a-z0-9]/gi, '').toUpperCase();
    return uuid.length === 34 ? uuid : '0x0';
}
NCUTCAT.tools.BufferToHex = (buffer) => {
    return '0x' + buffer.toString('hex').toUpperCase();
}

NCUTCAT.tools.utf8BufferToHex = (buffer) => NCUTCAT.tools.binaryStringToHexString(buffer.toString());

NCUTCAT.tools.binaryStringToHexString = (str) => {
    let buff = Buffer.from(str, 'binary');
    return '0x' + buff.toString('hex').toUpperCase();
}

const isDate_M = [0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];
NCUTCAT.tools.isDate = (date, allowDim) => {
    if (allowDim) //估计年龄
    {
        date = NCUTCAT.tools.AgeTool.toAgeData(date);
        if (!date) return false;
        else return NCUTCAT.tools.isDate(date.date);
    }
    let dim = false;
    if (date.endsWith('?')) {
        if (!allowDim) return false;
        date = date.substring(0, date.length - 1);
        dim = true;
    }
    let arr = date.replace(/-/g, '/').split('/', 4);
    let y, m, d;
    if (arr.length > 3) return false;
    if (!tool.inRange(y = parseInt(arr[0]), 1970, 9999)) return false;
    if (!tool.inRange(m = parseInt(arr[1]), 1, 12)) return false;
    if (!tool.inRange(d = parseInt(arr[2]), 1, isDate_M[m])) return false;

    let result = [y, m, d, dim];
    if (m != 2) return result;
    if ((!(y % 4) && (y % 100)) || !(y % 400)) return result;
    if (d < isDate_M[m]) return result;
    return false;
}

NCUTCAT.tools.toNumberDate = (date, allowDim) => {
    const r = tool.isDate(date, allowDim);
    if (r) {
        const y = r[0],
            m = r[1],
            d = r[2];
        return (r[3] ? -1 : 1) * (d + m * 100 + y * 10000);
    }
}

NCUTCAT.tools.newArray = (len, data) => {
    let arr = new Array(len);
    for (let i = 0; i < len; i++) arr[i] = data;
    return arr;
}

NCUTCAT.tools.AgeTool = {
    toAgeNumber: (date, estimate, extra) => {
        date = date.split('-');
        let y = parseInt(date[0]),
            m = parseInt(date[1]),
            d = parseInt(date[2]);
        console.log(estimate, y, m, d, extra);
        let num = estimate & 1;
        num = (num << 13) | (y & 8191);
        num = (num << 4) | (m & 15);
        num = (num << 5) | (d & 31);
        num = (num << 9) | (extra & 511);
        return num;
    },
    toAgeData: (num) => {
        num = parseInt(num);
        if (isNaN(num)) return null;
        let e = (num = num >>> 0) & ((1 << 9) - 1);
        let d = (num = num >>> 9) & ((1 << 5) - 1);
        let m = (num = num >>> 5) & ((1 << 4) - 1);
        let y = (num = num >>> 4) & ((1 << 13) - 1);
        let estimate = (num = num >>> 13) & 1;
        let p = (num, n) => (Array(n).join(0) + num).slice(-n);
        return {
            isEstimate: estimate,
            y: y,
            m: m,
            d: d,
            date: `${p(y,4)}-${p(m,2)}-${p(d,2)}`,
            extra: estimate ? e : 0,
            extraYear: estimate ? e / 12 | 0 : 0,
            extraMonth: estimate ? e % 12 : 0
        }
    }
}